package main


import (
	"fmt"
	"github.com/bytedance/sonic"
)


/*主题: [/1000100/400001/child/p2_4000010/properties/report] 
旧数据: 
{"deviceId":"p2_4000010","properties":{"accumulated_amount":118600,"active_power":118618, "A_current":0,"A_voltage":0,"B_current":0,"B_voltage":0,"C_current":0,"t":1747358721823}}","module":"report"}

新数据
{"deviceId":"p2_4000010","properties":{"accumulated_amount":118601,"active_power":118618, "A_current":0,"A_voltage":0,"B_current":0,"B_voltage":0,"C_current":0,"t":1747358721823}}","module":"report"}

对比新旧后得出变化的部分
{"deviceId":"p2_4000010","properties":{"accumulated_amount":118601,"t":1747358721823}}","module":"report"}

基于golang的json库  github.com/bytedance/sonic实现json对比*/

// DiffResult 差异结果结构
type DiffResult map[string]interface{}

// diffJSON 对比旧 JSON 和新 JSON，仅返回发生变化的字段
func diffJSON(oldStr, newStr string) (DiffResult, error) {
	var oldMap, newMap map[string]interface{}

	// 使用 sonic 进行高性能反序列化
	if err := sonic.Unmarshal([]byte(oldStr), &oldMap); err != nil {
		return nil, fmt.Errorf("unmarshal old error: %w", err)
	}
	if err := sonic.Unmarshal([]byte(newStr), &newMap); err != nil {
		return nil, fmt.Errorf("unmarshal new error: %w", err)
	}

	oldProps, ok1 := oldMap["properties"].(map[string]interface{})
	newProps, ok2 := newMap["properties"].(map[string]interface{})
	if !ok1 || !ok2 {
		return nil, fmt.Errorf("invalid 'properties' format")
	}

	changed := make(map[string]interface{})
	for key, newVal := range newProps {
		if oldVal, exists := oldProps[key]; !exists || oldVal != newVal {
			changed[key] = newVal
		}
	}

	if len(changed) == 0 {
		return nil, nil // 无变化
	}

	// 构造差异结果
	result := make(DiffResult)
	result["deviceId"] = newMap["deviceId"]
	result["properties"] = changed
	result["module"] = newMap["module"]
	return result, nil
}

func main() {
	oldJSON := `{"deviceId":"p2_4000010","properties":{"accumulated_amount":118600,"active_power":118618, "A_current":0,"A_voltage":0,"B_current":0,"B_voltage":0,"C_current":0,"t":1747358721820},"module":"report"}`
	newJSON := `{"deviceId":"p2_4000010","properties":{"accumulated_amount":118601,"active_power":118618, "A_current":0,"A_voltage":0,"B_current":1,"B_voltage":0,"C_current":0,"t":1747358721823},"module":"report"}`

	result, err := diffJSON(oldJSON, newJSON)
	if err != nil {
		fmt.Println("Error:", err)
		return
	}
	if result != nil {
		diffStr, _ := sonic.MarshalString(result)
		fmt.Println("Changed Fields:", diffStr)
	} else {
		fmt.Println("No change detected")
	}
}
